package cn.com.shopec.erp.stock.service.impl;

import java.util.ArrayList;
import java.util.List;

import javax.annotation.Resource;

import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import cn.com.shopec.erp.common.constant.SZSCMConstant;
import cn.com.shopec.erp.common.orm.impl.HibernateEntityDao;
import cn.com.shopec.erp.common.page.PageFinder;
import cn.com.shopec.erp.common.page.PageQuery;
import cn.com.shopec.erp.common.utils.DateUtil;
import cn.com.shopec.erp.common.utils.IntegerUtil;
import cn.com.shopec.erp.common.utils.StringUtil;
import cn.com.shopec.erp.stock.commo.ObjectUtil;
import cn.com.shopec.erp.stock.commo.StockProductException;
import cn.com.shopec.erp.stock.dao.IProductBarCodeDao;
import cn.com.shopec.erp.stock.dao.IStockInProductDao;
import cn.com.shopec.erp.stock.dao.IStockOutProductDao;
import cn.com.shopec.erp.stock.entity.ProductBarCode;
import cn.com.shopec.erp.stock.entity.StockOutProduct;
import cn.com.shopec.erp.stock.service.IProductBarCodeService;
import cn.com.shopec.erp.stock.vo.ProductBarCodeVo;
import cn.com.shopec.erp.system.common.UserUtils;

@Service
public class ProductBarCodeServiceImpl extends HibernateEntityDao<StockOutProduct> implements IProductBarCodeService {

	@Resource
	private IStockInProductDao stockInProductDao;

	@Resource
	private IStockOutProductDao stockOutProductDao;

	@Resource
	private IProductBarCodeDao productBarCodeDao;
	
	/** 条形码已经出库 **/
	private final int BARCODE_IS_STOCKOUT = 4;
	
	/** 条形码商品不在此仓库 **/
	private final int BARCODE_WAREHOUSE_NO_IDENTICAL = 3;
	
	/** 条形码与商品不一致 **/
	private final int BARCODE_PRODUCT_NO_IDENTICAL = 2;
	
	/** 条形码不存在 **/
	private final int BARCODE_NO_EXSITS = 1;

	@Override
	public PageFinder<ProductBarCodeVo> queryProductBarCodeList(ProductBarCodeVo productBarCode, PageQuery pageQuery) {
		int count = productBarCodeDao.getProductsCount(productBarCode);
		PageFinder<ProductBarCodeVo> result = new PageFinder<ProductBarCodeVo>(pageQuery.getPage(),
				pageQuery.getPageSize(), count);
		if (IntegerUtil.gtZero(count)) {
			List<ProductBarCodeVo> stockHistoryVos = productBarCodeDao.getProductsList(productBarCode,
					result.getStartOfPage(), result.getPageSize());
			result.setData(stockHistoryVos);
		}
		return result;
	}

	@Override
	@Transactional
	public void addProductBarCode(List<ProductBarCode> productBarCodes) throws Exception {
		for (ProductBarCode productBarCode : productBarCodes) {
			addProductBarCode(productBarCode);
		}
	}

	@Override
	@Transactional
	public boolean addProductBarCode(ProductBarCode productBarCode) throws Exception {
		if (ObjectUtil.isNotNull(productBarCode)) {
			productBarCode.setId(null);
			productBarCode.setCreater(UserUtils.getLoginUserName());
			productBarCode.setCreateTime(DateUtil.parseSqlDate(DateUtil.getCurrentDate()));
			productBarCode.setEffectiveState(SZSCMConstant.DELETE_FLAG_NO);
			productBarCode.setDeletedFlag(SZSCMConstant.DELETE_FLAG_NO);
			productBarCodeDao.save(productBarCode);
			return true;
		}
		return false;
	}

	@Override
	@Transactional
	public boolean StockOutProductBarCode(String codeNo) throws Exception {
		ProductBarCode productBarCode = productBarCodeDao.findUniqueBy("codeNo", codeNo);
		if (ObjectUtil.isNotNull(productBarCode)) {
			// productBarCode.setStockOutState(1);
			productBarCode.setUpdater(UserUtils.getLoginUserName());
			productBarCode.setUpdateTime(DateUtil.parseSqlDate(DateUtil.getCurrentDate()));
			productBarCodeDao.update(productBarCode);
			return true;
		}
		return false;
	}

	@Override
	@Transactional
	public void deleteProductBarCode(String stockInProductId) throws Exception {
		productBarCodeDao.deleteBarCodeForProductId(stockInProductId);
		stockInProductDao.setProductCodeIsImport(stockInProductId, SZSCMConstant.PRODUCT_PUR_STATE_0);
	}

	@Override
	@Transactional
	public void importProductBarCodes(ProductBarCode productBarCode, List<Object> excelData) throws Exception {
		boolean isOrderReturn = ObjectUtil.eq(productBarCode.getStockInType(), SZSCMConstant.STOCKIN_TYPE_2);
		for (Object object : excelData) {
			ProductBarCode productBarCodeTemp = (ProductBarCode) object;
			productBarCodeTemp.setProdNo(productBarCode.getProdNo());
			productBarCodeTemp.setStockInNo(productBarCode.getStockInNo());
			productBarCodeTemp.setStockInProductId(productBarCode.getStockInProductId());
			productBarCodeTemp.setCommoNo(productBarCode.getCommoNo());
			productBarCodeTemp.setWhNo(productBarCode.getWhNo());
			productBarCodeTemp.setSupNo(productBarCode.getSupNo());
			productBarCodeTemp.setPurNo(productBarCode.getPurNo());
			productBarCodeTemp.setStockInType(productBarCode.getStockInType());
			productBarCodeTemp.setStockInTypeNo(productBarCode.getStockInTypeNo());
			productBarCodeTemp.setProdQuantity(1l);
			productBarCodeTemp.setCreater(UserUtils.getLoginUserName());
			productBarCodeTemp.setCreateTime(DateUtil.parseSqlDate(DateUtil.getCurrentDate()));
			productBarCodeTemp.setEffectiveState(SZSCMConstant.DELETE_FLAG_NO);
			productBarCodeTemp.setDeletedFlag(SZSCMConstant.DELETE_FLAG_NO);
			ProductBarCode productBarCodeFormDB = productBarCodeDao
					.getNoStockOutBarCode(productBarCodeTemp.getCodeNo());
			if (!isOrderReturn && ObjectUtil.isNull(productBarCodeFormDB)) {
				productBarCodeDao.save(productBarCodeTemp);
			} else if (isOrderReturn && !ObjectUtil.isNull(productBarCodeFormDB)
					&& !StringUtil.isEmpty(productBarCodeFormDB.getStockOutNo())) {
				productBarCodeTemp.setPurNo(productBarCodeFormDB.getPurNo());
				productBarCodeDao.save(productBarCodeTemp);
				// 新增后要将原出库的数据变为无效数据（既历史数据）
				// productBarCodeDao.setBarCodeEffectiveState(productBarCodeTemp.getId(),productBarCodeFormDB.getCodeNo(),SZSCMConstant.DELETE_FLAG_YES);
			} else {
				throw new StockProductException(productBarCodeTemp, productBarCode.getStockInType());
			}
		}
		stockInProductDao.setProductCodeIsImport(productBarCode.getStockInProductId(),
				SZSCMConstant.PRODUCT_PUR_STATE_1);
	}

	/*@Override
	@Transactional
	public Map<String, Object> checkBarCodeForStockOut(ProductBarCode productBarCode, List<Object> excelData) {
		Map<String, Object> result = null;
		List<ProductBarCode> correctCodes = new ArrayList<ProductBarCode>();
		List<ProductBarCode> stockedOutCodes = new ArrayList<ProductBarCode>();
		List<ProductBarCode> noExistsCodes = new ArrayList<ProductBarCode>();
		for (Object object : excelData) {
			ProductBarCode productBarCodeTemp = (ProductBarCode) object;
			ProductBarCode productBarCodeFromDB = productBarCodeDao
					.getNoStockOutBarCode(productBarCodeTemp.getCodeNo());
			if (ObjectUtil.isNull(productBarCodeFromDB)) {
				noExistsCodes.add(productBarCodeTemp);
			} else if (!StringUtil.isEmpty(productBarCodeFromDB.getStockOutNo())) {
				stockedOutCodes.add(productBarCodeFromDB);
			} else {
				correctCodes.add(productBarCodeFromDB);
			}
		}
		if (stockedOutCodes.size() > 0 || noExistsCodes.size() > 0) {
			result = new HashMap<String, Object>();
			result.put("correctCodes", correctCodes);
			result.put("stockedOutCodes", stockedOutCodes);
			result.put("noExistsCodes", noExistsCodes);
		} else {
			setBarCodeStockOut(productBarCode, correctCodes);
		}
		return result;
	}
*/
	@Override
	@Transactional
	public ProductBarCodeVo checkBarCodeForStockOut(ProductBarCode productBarCode, List<Object> excelData) {
		List<ProductBarCode> correctCodes = new ArrayList<ProductBarCode>();
		ProductBarCodeVo result = new ProductBarCodeVo();
		for (Object object : excelData) {
			ProductBarCode productBarCodeTemp = (ProductBarCode) object;
			result.setCodeNo(productBarCodeTemp.getCodeNo());
			ProductBarCode productBarCodeFromDB = productBarCodeDao
					.getNoStockOutBarCode(productBarCodeTemp.getCodeNo());
			if (ObjectUtil.isNull(productBarCodeFromDB)) {
				result.setErrorReason(BARCODE_NO_EXSITS);
				return result;
			} else if (!ObjectUtil.eq(productBarCode.getProdNo(), productBarCodeFromDB.getProdNo())) {
				result.setErrorReason(BARCODE_PRODUCT_NO_IDENTICAL);
				return result;
			} else if (!ObjectUtil.eq(productBarCode.getWhNo(), productBarCodeFromDB.getWhNo())) {
				result.setErrorReason(BARCODE_WAREHOUSE_NO_IDENTICAL);
				return result;
			} else if (!StringUtil.isEmpty(productBarCodeFromDB.getStockOutNo())) {
				result.setErrorReason(BARCODE_IS_STOCKOUT);
				return result;
			} else {
				correctCodes.add(productBarCodeFromDB);
			}
		}
		setBarCodeStockOut(productBarCode, correctCodes);
		return null;// 返回代表条形码无误
	}

	@Transactional
	public void setBarCodeStockOut(ProductBarCode productBarCode, List<ProductBarCode> productBarCodes) {
		productBarCodeDao.setBarCodeStockOut(productBarCode, productBarCodes);
		stockOutProductDao.setProductCodeIsImport(productBarCode.getStockOutProductId(),
				SZSCMConstant.PRODUCT_PUR_STATE_1);
	}

	@Override
	@Transactional
	public void cancelBarCodeStateStockOut(String stockOutProductId) {
		productBarCodeDao.cancelBarCodeStateStockOut(stockOutProductId);
		stockOutProductDao.setProductCodeIsImport(stockOutProductId, SZSCMConstant.PRODUCT_PUR_STATE_0);
	}

	@Override
	@Transactional
	public List<ProductBarCode> checkBarCodeForPurReturn(ProductBarCode productBarCode, List<Object> excelData) {
		List<ProductBarCode> noExistsCodes = new ArrayList<ProductBarCode>();
		for (Object object : excelData) {
			ProductBarCode productBarCodeTemp = (ProductBarCode) object;
			String code = productBarCodeTemp.getCodeNo();
			if (StringUtil.isEmpty(code)) {
				productBarCode = stockOutProductDao.getProductCodeBycode(code);
				if (ObjectUtil.isNotNull(productBarCode)) {
					stockOutProductDao.setProductCodeIsNoEffective(productBarCode.getId(),
							SZSCMConstant.DELETE_FLAG_YES);
					productBarCodeTemp.setStockInNo(productBarCode.getStockInNo());
					productBarCodeTemp.setStockInProductId(productBarCode.getStockInProductId());
					productBarCodeTemp.setProdNo(productBarCode.getProdNo());
					productBarCodeTemp.setCommoNo(productBarCode.getCommoNo());
					productBarCodeTemp.setWhNo(productBarCode.getWhNo());
					productBarCodeTemp.setSupNo(productBarCode.getSupNo());
					productBarCodeTemp.setPurNo(productBarCode.getPurNo());
					productBarCodeTemp.setStockInType(productBarCode.getStockInType());
					productBarCodeTemp.setStockInTypeNo(productBarCode.getStockInTypeNo());
					productBarCodeTemp.setProdQuantity(productBarCode.getProdQuantity());
					productBarCodeTemp.setCreater(UserUtils.getLoginUserName());
					productBarCodeTemp.setCreateTime(DateUtil.parseSqlDate(DateUtil.getCurrentDate()));
					productBarCodeTemp.setEffectiveState(SZSCMConstant.DELETE_FLAG_NO);
					productBarCodeTemp.setDeletedFlag(SZSCMConstant.DELETE_FLAG_NO);
				} else {
					noExistsCodes.add(productBarCodeTemp);
				}
			}
		}
		return noExistsCodes;
	}

}
